package wonder;

import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;

import org.slf4j.Logger;

import wonder.tools.LoggerHelper;

/**
 * <p>SWServiceFactory class.</p>
 *
 * @author u211354
 * @version $Id: $
 */
public class SWServiceFactory {
    private static final Logger logger = LoggerHelper.getLogger();
    private static SWServiceFactory instance;
    private final Map<String,ISWService> cache;

    private SWServiceFactory() throws Exception {
        super();
        cache = new HashMap<String,ISWService>();
    }

    /**
     * <p>Getter for the field <code>instance</code>.</p>
     *
     * @return a {@link wonder.SWServiceFactory} object.
     * @throws java.lang.Exception if any.
     */
    public static synchronized SWServiceFactory getInstance() throws Exception {
        // @formatter:off
        if (instance == null)
            instance = new SWServiceFactory();
        // @formatter:on
        return instance;
    }

    /**
     * <p>configure</p>
     *
     * @param file a {@link java.lang.String} object.
     * @throws java.lang.Exception if any.
     */
    public void configure(String file) throws Exception {
        synchronized (this) {
            SWConfigResource.loadResource(file);
            cache.clear();
        }
    }

    /**
     * <p>configure</p>
     *
     * @param in a {@link java.io.InputStream} object.
     * @throws java.lang.Exception if any.
     */
    public void configure(InputStream in) throws Exception {
        synchronized (this) {
            SWConfigResource.loadResource(in);
            cache.clear();
        }
    }

    /**
     * <p>getSWService</p>
     *
     * @return a {@link wonder.ISWService} object.
     * @throws java.lang.Exception if any.
     */
    public ISWService getSWService() throws Exception {
        String library = SWConfigResource.getParamString("library");
        if (library == null) {
            logger.debug("", SWConfigResource.getMap());
            return null;
        }

        synchronized (this) {
            ISWService as = cache.get(library);
            if (as == null) {
                logger.debug("ISWService class: {}", library);
                as = (ISWService)Class.forName(library).newInstance();
                as.configure(SWConfigResource.getMap());
                cache.put(library, as);
            }
            return as;
        }
    }

    /**
     * <p>
     * releaseAuditService.
     * </p>
     *
     * @throws java.lang.Exception if any.
     */
    public void releaseSWService() throws Exception {
        synchronized (this) {
            logger.debug("Releasing ISWService");
            getSWService().release();
            cache.clear();
        }
    }
}
